using System;
using System.Collections;
using System.Collections.ObjectModel;
using System.Collections.Generic;
using System.ComponentModel;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Shapes;

namespace Microsoft.PowerShell.CmdletManagement
{
    /// <summary>
    /// Interaction logic for ImportParameter.xaml
    /// </summary>

    public partial class ImportParameter : System.Windows.Window
    {
        ObservableCollection<PsSpecCmdletParameterGroupEntry> topParameters = new ObservableCollection<PsSpecCmdletParameterGroupEntry>();
        ObservableCollection<PsSpecCmdletParameterGroupEntry> selectedParameters = new ObservableCollection<PsSpecCmdletParameterGroupEntry>();

        public ImportParameter(string currentProject, string serviceUri, Window owner)
        {
            this.currentProject = currentProject;
            this.serviceUri = serviceUri;

            InitializeComponent();

            PopulateTopParameters();

            ParameterList.DataContext = topParameters;
            SelectedItems.DataContext = selectedParameters;

            this.Owner = owner;
        }

        private string serviceUri;
        private string currentProject;

        public ObservableCollection<PsSpecCmdletParameterGroupEntry> SelectedParameters
        {
            get { return selectedParameters; }
        }

        private ICollectionView CollectionView
        {
            get
            {
                if (collectionView == null)
                {
                    lock (lockObject)
                    {
                        if (collectionView == null)
                        {
                            collectionView = CollectionViewSource.GetDefaultView(ParameterList.DataContext);

                            if (collectionView != null)
                            {
                                collectionView.Filter = new Predicate<object>(TextFilter);
                            }
                        }
                    }
                }

                return collectionView;
            }
        }
        ICollectionView collectionView = null;
        private object lockObject = new object();

        protected bool TextFilter(object item)
        {
            PsSpecCmdletParameterGroupEntry groupEntry = item as PsSpecCmdletParameterGroupEntry;

            if(
                (groupEntry == null) ||
                (String.IsNullOrEmpty(Search.Text)) ||
                (Search.Text == "Search") ||
                (groupEntry.ParameterName.IndexOf(Search.Text, StringComparison.InvariantCultureIgnoreCase) >= 0) ||
                (groupEntry.Type.IndexOf(Search.Text, StringComparison.InvariantCultureIgnoreCase) >= 0) ||
                (("" + groupEntry.Description).IndexOf(Search.Text, StringComparison.InvariantCultureIgnoreCase) >= 0))
            {
                return true;
            }
            else
            {
                return false;
            }
        }

        private void PopulateTopParameters()
        {
            // Get the parameter grouping entries
            GetPsSpecCmdletParameterGroupEntryCommand command = new GetPsSpecCmdletParameterGroupEntryCommand();
            if ((ThisProject.IsChecked == true) && (! String.IsNullOrEmpty(currentProject)))
            {
                command.ProjectName = currentProject;
            }

            command.ServiceUri = serviceUri;

            try
            {
                topParameters.Clear();
                foreach (PsSpecCmdletParameterGroupEntry result in command.Invoke())
                {
                    topParameters.Add(result);
                }
            }
            catch (Exception exception)
            {
                MessageBox.Show(exception.Message);
            }

            CmdletDesignerUtils.ResizeColumns(ParameterList, "Type");
        }

        private void ParameterList_SizeChanged(Object sender, EventArgs e)
        {
            CmdletDesignerUtils.ResizeColumns(ParameterList, "Type");
        }

        // They've clicked "Add"
        private void Click_Add(Object sender, RoutedEventArgs e)
        {
            List<PsSpecCmdletParameterGroupEntry> removedItems = new List<PsSpecCmdletParameterGroupEntry>();

            foreach (PsSpecCmdletParameterGroupEntry item in ParameterList.SelectedItems)
            {
                if (!selectedParameters.Contains(item))
                {
                    selectedParameters.Add(item);
                    removedItems.Add(item);
                }
            }

            foreach (PsSpecCmdletParameterGroupEntry removedItem in removedItems)
            {
                topParameters.Remove(removedItem);
            }
        }

        // They've clicked "Remove"
        private void Click_Remove(Object sender, RoutedEventArgs e)
        {
            List<PsSpecCmdletParameterGroupEntry> removedItems = new List<PsSpecCmdletParameterGroupEntry>();

            foreach (PsSpecCmdletParameterGroupEntry item in SelectedItems.SelectedItems)
            {
                topParameters.Add(item);
                removedItems.Add(item);
            }

            foreach (PsSpecCmdletParameterGroupEntry removedItem in removedItems)
            {
                selectedParameters.Remove(removedItem);
            }
        }

        // They've clicked "Import"
        private void Click_Import(Object sender, RoutedEventArgs e)
        {
            this.DialogResult = true;
            this.Close();
        }

        // They've clicked "Cancel"
        private void Click_Cancel(Object sender, RoutedEventArgs e)
        {
            this.DialogResult = false;
            this.Close();
        }

        // They've changed the project options
        private void ProjectButton_Checked(Object sender, EventArgs e)
        {
            PopulateTopParameters();
        }

        // They've changed the search text
        private void Search_TextChanged(Object sender, EventArgs e)
        {
            if (ParameterList != null)
            {
                ICollectionView collectionView = CollectionView;
                if (collectionView != null)
                {
                    collectionView.Refresh();
                }
            }
        }

        // They focused on the search box
        private void Search_GotFocus(Object sender, EventArgs e)
        {
            Search.Foreground = Brushes.Black;

            if (Search.Text == "Search")
            {
                Search.Text = "";
            }
        }

        private void Search_LostFocus(Object sender, EventArgs e)
        {
            Search.Foreground = new SolidColorBrush(Color.FromArgb(128, 0, 0, 0));

            if (String.IsNullOrEmpty(Search.Text) || (Search.Text == "Search"))
            {
                Search.Text = "Search";
            }
        }
   }
}